﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using Microsoft.Xna.Framework;
using Microsoft.Xna.Framework.Input;
using Microsoft.Xna.Framework.Graphics;
using Afru;

namespace Afru
{
    public class GamePadManager : Component
    {
       /// <summary>
       /// Manages gamepad input for ease of use. ControllerNum is indexed from 1 to 4.
       /// </summary>
        #region Variables

        GamePadState[] PreviousState = new GamePadState[4];
        GamePadState[] CurrentState = new GamePadState[4];

        #endregion

        #region Constructor

        public GamePadManager()
        {
            PreviousState[0] = GamePad.GetState(PlayerIndex.One);
            PreviousState[1] = GamePad.GetState(PlayerIndex.Two);
            PreviousState[2] = GamePad.GetState(PlayerIndex.Three);
            PreviousState[3] = GamePad.GetState(PlayerIndex.Four);

            CurrentState[0] = GamePad.GetState(PlayerIndex.One);
            CurrentState[1] = GamePad.GetState(PlayerIndex.Two);
            CurrentState[2] = GamePad.GetState(PlayerIndex.Three);
            CurrentState[3] = GamePad.GetState(PlayerIndex.Four);

            this.Visible = false;
        }

        #endregion

        #region Class functions

        //triggers
        public float LeftTriggerVal(int ControllerNum)
        {
            return CurrentState[ControllerNum - 1].Triggers.Left;
        }
        public float RightTrigerVal(int ControllerNum)
        {
            return CurrentState[ControllerNum - 1].Triggers.Right;
        }
        public bool LeftTriggerPre(int ControllerNum)
        {
            return ((PreviousState[ControllerNum - 1].Triggers.Left == 0.0f) && (CurrentState[ControllerNum - 1].Triggers.Left > 0.0f));
        }
        public bool RightTriggerPre(int ControllerNum)
        {
            return ((PreviousState[ControllerNum - 1].Triggers.Right == 0.0f) && (CurrentState[ControllerNum - 1].Triggers.Right > 0.0f));
        }
        public bool LeftTriggerRel(int ControllerNum)
        {
            return ((PreviousState[ControllerNum - 1].Triggers.Left > 0.0f) && (CurrentState[ControllerNum - 1].Triggers.Left == 0.0f));
        }
        public bool RightTriggerRel(int ControllerNum)
        {
            return ((PreviousState[ControllerNum - 1].Triggers.Right > 0.0f) && (CurrentState[ControllerNum - 1].Triggers.Right == 0.0f));
        }

        //bumpers
        public bool LeftBumberPre(int ControllerNum)
        {
            return ((PreviousState[ControllerNum - 1].Buttons.LeftShoulder == ButtonState.Released) && (CurrentState[ControllerNum - 1].Buttons.LeftShoulder == ButtonState.Pressed));
        }
        public bool RightBumberPre(int ControllerNum)
        {
            return ((PreviousState[ControllerNum - 1].Buttons.RightShoulder == ButtonState.Released) && (CurrentState[ControllerNum - 1].Buttons.RightShoulder == ButtonState.Pressed));
        }
        public bool LeftBumberRel(int ControllerNum)
        {
            return ((PreviousState[ControllerNum - 1].Buttons.LeftShoulder == ButtonState.Pressed) && (CurrentState[ControllerNum - 1].Buttons.LeftShoulder == ButtonState.Released));
        }
        public bool RightBumberRel(int ControllerNum)
        {
            return ((PreviousState[ControllerNum - 1].Buttons.RightShoulder == ButtonState.Pressed) && (CurrentState[ControllerNum - 1].Buttons.RightShoulder == ButtonState.Released));
        }
        public bool LeftBumberHeld(int ControllerNum)
        {
            return (CurrentState[ControllerNum - 1].Buttons.LeftShoulder == ButtonState.Pressed);
        }
        public bool RightBumberHeld(int ControllerNum)
        {
            return (CurrentState[ControllerNum - 1].Buttons.RightShoulder == ButtonState.Pressed);
        }

        //Sticks
        public Vector2 LeftStick(int ControllerNum)
        {
            return CurrentState[ControllerNum - 1].ThumbSticks.Left;
        }
        public Vector2 RightStick(int ControllerNum)
        {
            return CurrentState[ControllerNum - 1].ThumbSticks.Right;
        }
        public int LeftStickDirection(int ControllerNum)
        {
            float _x = CurrentState[ControllerNum - 1].ThumbSticks.Left.X, _y = CurrentState[ControllerNum - 1].ThumbSticks.Left.Y;
            return (int)Math.Atan(_y / _x);
        }
        public int RightStickDirection(int ControllerNum)
        {
            float _x = CurrentState[ControllerNum - 1].ThumbSticks.Right.X, _y = CurrentState[ControllerNum - 1].ThumbSticks.Right.Y;
            return (int)Math.Atan(_y / _x);
        }
        public bool LeftStickPressed(int ControllerNum)
        {
            return ((PreviousState[ControllerNum - 1].Buttons.LeftStick == ButtonState.Released) && (CurrentState[ControllerNum - 1].Buttons.LeftStick == ButtonState.Pressed));
        }
        public bool RightStickPressed(int ControllerNum)
        {
            return ((PreviousState[ControllerNum - 1].Buttons.RightStick == ButtonState.Released) && (CurrentState[ControllerNum - 1].Buttons.RightStick == ButtonState.Pressed));
        }
        public bool LeftStickReleased(int ControllerNum)
        {
            return ((PreviousState[ControllerNum - 1].Buttons.LeftStick == ButtonState.Pressed) && (CurrentState[ControllerNum - 1].Buttons.LeftStick == ButtonState.Released));
        }
        public bool RightStickReleased(int ControllerNum)
        {
            return ((PreviousState[ControllerNum - 1].Buttons.RightStick == ButtonState.Pressed) && (CurrentState[ControllerNum - 1].Buttons.RightStick == ButtonState.Released));
        }
        public bool LeftStickHeld(int ControllerNum)
        {
            return (CurrentState[ControllerNum - 1].Buttons.LeftStick == ButtonState.Pressed);
        }
        public bool RightStickHeld(int ControllerNum)
        {
            return (CurrentState[ControllerNum - 1].Buttons.RightStick == ButtonState.Pressed);
        }

        //DPad
        public bool LeftPressed(int ControllerNum)
        {
            return ((PreviousState[ControllerNum - 1].DPad.Left == ButtonState.Released) && (CurrentState[ControllerNum - 1].DPad.Left == ButtonState.Pressed));
        }
        public bool LeftReleased(int ControllerNum)
        {
            return ((PreviousState[ControllerNum - 1].DPad.Left == ButtonState.Pressed) && (CurrentState[ControllerNum - 1].DPad.Left == ButtonState.Released));
        }
        public bool LeftHeld(int ControllerNum)
        {
            return (CurrentState[ControllerNum - 1].DPad.Left == ButtonState.Pressed);
        }
        public bool RightPressed(int ControllerNum)
        {
            return ((PreviousState[ControllerNum - 1].DPad.Right == ButtonState.Released) && (CurrentState[ControllerNum - 1].DPad.Right == ButtonState.Pressed));
        }
        public bool RightReleased(int ControllerNum)
        {
            return ((PreviousState[ControllerNum - 1].DPad.Right == ButtonState.Pressed) && (CurrentState[ControllerNum - 1].DPad.Right == ButtonState.Released));
        }
        public bool RightHeld(int ControllerNum)
        {
            return (CurrentState[ControllerNum - 1].DPad.Right == ButtonState.Pressed);
        }
        public bool UpPressed(int ControllerNum)
        {
            return ((PreviousState[ControllerNum - 1].DPad.Up == ButtonState.Released) && (CurrentState[ControllerNum - 1].DPad.Up == ButtonState.Pressed));
        }
        public bool UpReleased(int ControllerNum)
        {
            return ((PreviousState[ControllerNum - 1].DPad.Up == ButtonState.Pressed) && (CurrentState[ControllerNum - 1].DPad.Up == ButtonState.Released));
        }
        public bool UpHeld(int ControllerNum)
        {
            return (CurrentState[ControllerNum - 1].DPad.Up == ButtonState.Pressed);
        }
        public bool DownPressed(int ControllerNum)
        {
            return ((PreviousState[ControllerNum - 1].DPad.Down == ButtonState.Released) && (CurrentState[ControllerNum - 1].DPad.Down == ButtonState.Pressed));
        }
        public bool DownReleased(int ControllerNum)
        {
            return ((PreviousState[ControllerNum - 1].DPad.Down == ButtonState.Pressed) && (CurrentState[ControllerNum - 1].DPad.Down == ButtonState.Released));
        }
        public bool DownHeld(int ControllerNum)
        {
            return (CurrentState[ControllerNum - 1].DPad.Down == ButtonState.Pressed);
        }

        //ABXY
        public bool XPressed(int ControllerNum)
        {
            return ((PreviousState[ControllerNum - 1].Buttons.X == ButtonState.Released) && (CurrentState[ControllerNum - 1].Buttons.X == ButtonState.Pressed));
        }
        public bool XReleased(int ControllerNum)
        {
            return ((PreviousState[ControllerNum - 1].Buttons.X == ButtonState.Pressed) && (CurrentState[ControllerNum - 1].Buttons.X == ButtonState.Released));
        }
        public bool XHeld(int ControllerNum)
        {
            return (CurrentState[ControllerNum - 1].Buttons.X == ButtonState.Pressed);
        }
        public bool YPressed(int ControllerNum)
        {
            return ((PreviousState[ControllerNum - 1].Buttons.Y == ButtonState.Released) && (CurrentState[ControllerNum - 1].Buttons.Y == ButtonState.Pressed));
        }
        public bool YReleased(int ControllerNum)
        {
            return ((PreviousState[ControllerNum - 1].Buttons.Y == ButtonState.Pressed) && (CurrentState[ControllerNum - 1].Buttons.Y == ButtonState.Released));
        }
        public bool YHeld(int ControllerNum)
        {
            return (CurrentState[ControllerNum - 1].Buttons.Y == ButtonState.Pressed);
        }
        public bool APressed(int ControllerNum)
        {
            return ((PreviousState[ControllerNum - 1].Buttons.A == ButtonState.Released) && (CurrentState[ControllerNum - 1].Buttons.A == ButtonState.Pressed));
        }
        public bool AReleased(int ControllerNum)
        {
            return ((PreviousState[ControllerNum - 1].Buttons.A == ButtonState.Pressed) && (CurrentState[ControllerNum - 1].Buttons.A == ButtonState.Released));
        }
        public bool AHeld(int ControllerNum)
        {
            return (CurrentState[ControllerNum - 1].Buttons.A == ButtonState.Pressed);
        }
        public bool BPressed(int ControllerNum)
        {
            return ((PreviousState[ControllerNum - 1].Buttons.B == ButtonState.Released) && (CurrentState[ControllerNum - 1].Buttons.B == ButtonState.Pressed));
        }
        public bool BReleased(int ControllerNum)
        {
            return ((PreviousState[ControllerNum - 1].Buttons.B == ButtonState.Pressed) && (CurrentState[ControllerNum - 1].Buttons.B == ButtonState.Released));
        }
        public bool BHeld(int ControllerNum)
        {
            return (CurrentState[ControllerNum - 1].Buttons.B == ButtonState.Pressed);
        }

        //Start/Back
        public bool StartPressed(int ControllerNum)
        {
            return ((PreviousState[ControllerNum - 1].Buttons.Start == ButtonState.Released) && (CurrentState[ControllerNum - 1].Buttons.Start == ButtonState.Pressed));
        }
        public bool StartReleased(int ControllerNum)
        {
            return ((PreviousState[ControllerNum - 1].Buttons.Start == ButtonState.Pressed) && (CurrentState[ControllerNum - 1].Buttons.Start == ButtonState.Released));
        }
        public bool StartHeld(int ControllerNum)
        {
            return (CurrentState[ControllerNum - 1].Buttons.Start == ButtonState.Pressed);
        }
        public bool BackPressed(int ControllerNum)
        {
            return ((PreviousState[ControllerNum - 1].Buttons.Back == ButtonState.Released) && (CurrentState[ControllerNum - 1].Buttons.Back == ButtonState.Pressed));
        }
        public bool BackReleased(int ControllerNum)
        {
            return ((PreviousState[ControllerNum - 1].Buttons.Back == ButtonState.Pressed) && (CurrentState[ControllerNum - 1].Buttons.Back == ButtonState.Released));
        }
        public bool BackHeld(int ControllerNum)
        {
            return (CurrentState[ControllerNum - 1].Buttons.Back == ButtonState.Pressed);
        }

        #endregion

        #region Overridden functions

        public override void Update()
        {
            PreviousState[0] = CurrentState[0];
            PreviousState[1] = CurrentState[1];
            PreviousState[2] = CurrentState[2];
            PreviousState[3] = CurrentState[3];

            CurrentState[0] = GamePad.GetState(PlayerIndex.One);
            CurrentState[1] = GamePad.GetState(PlayerIndex.Two);
            CurrentState[2] = GamePad.GetState(PlayerIndex.Three);
            CurrentState[3] = GamePad.GetState(PlayerIndex.Four);

            base.Update();
        }

        #endregion

    }
}
